﻿using System.Web.Http;
using System.Web.Http.Dispatcher;
using System.Web.Mvc;
using System.Web.Routing;
using Autofac;
using Autofac.Integration.Mvc;
using Freedom.Framework.Mvc.Controller;
using Freedom.Framework.Mvc.Filter;
using Freedom.Framework.Mvc.Routes;
using Freedom.Framework.Mvc.View;

namespace Freedom.Framework.Mvc
{
    public abstract class AutofacApplication : System.Web.HttpApplication
    {
        protected virtual IContainer CreateContainer()
        {
            var builder = RegisterComponentConfig.GetBuilder();
            RegisterServices(builder);
            RegisterRepository(builder);
            return builder.Build();
        }

        protected abstract void RegisterServices(ContainerBuilder builder);
        protected abstract void RegisterRepository(ContainerBuilder builder);

        protected void Application_Start()
        {
            //config the log4net
            log4net.Config.XmlConfigurator.Configure();

            var container = CreateContainer();

            //repalce the controller factory to make sure use the module controllers
            ControllerBuilder.Current.SetControllerFactory(new FreedomControllerFactory(container));
            DependencyResolver.SetResolver(new AutofacDependencyResolver(container));

            //get the web api type from module
            GlobalConfiguration.Configuration.Services.Replace(typeof (IHttpControllerSelector),
                                                               new AreaHttpControllerSelector(GlobalConfiguration.Configuration, container));
            GlobalConfiguration.Configuration.DependencyResolver =
                new Autofac.Integration.WebApi.AutofacWebApiDependencyResolver(container);

            //use the new vew engine to add the module view files
            ViewEngines.Engines.Clear();
            ViewEngines.Engines.Add(new EnhanceRazorViewEngine());

            //register each module api controller route
            WebApiConfig.Register(GlobalConfiguration.Configuration, container);
            //register each module controller route
            RouteConfig.RegisterRoutes(RouteTable.Routes, container);

            //register the filters
            FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);

            OnApplicationStarted();
        }

        protected virtual void OnApplicationStarted() { }
    }
}
